<?php
namespace App\Services;

use App\Models\User;
use Illuminate\Auth\AuthenticationException;
use Overtrue\Socialite\AccessToken;
use Illuminate\Support\Str;
class AuthorizationSocialService{
    //获取unionid和openid
    /*
     * $type 请求类型 目前仅支持weimini、wechat
     * $request code 或者第三方服务器返回的一系列数据
     */
    public function getThirdId($type,$request){
        if($type!="weimini"){
            $driver = \Socialite::driver($type);
        }
        switch ($type){
            case 'wechat':
                try {
                    if ($code = $request->code) {
                        $accessToken = $driver->getAccessToken($code);
                    } else {
                        $tokenData['access_token'] = $request->access_token;

                        // 微信需要增加 openid
                        $tokenData['openid'] = $request->openid;
                        $accessToken = new AccessToken($tokenData);
                    }

                    $oauthUser = $driver->user($accessToken);
                    $data['unionid'] = $oauthUser->getOriginal()['unionid'] ?? null;
                    $data['openid'] = $oauthUser->getId();
                    $data['session_key'] = $accessToken;
                    $data['avatar'] = $oauthUser->getAvatar();
                }catch (\Exception $e){
                    throw new AuthenticationException($e);
                }
                break;
            case "weimini":
                $miniProgram = \EasyWeChat::miniProgram();
                $oauthUser = $miniProgram->auth->session($request->code);
                // 如果结果错误，说明 code 已过期或不正确，返回 401 错误
                if (isset($oauthUser['errcode'])) {
                    throw new AuthenticationException($oauthUser['errcode']);
                }

                $data['unionid'] = $oauthUser['unionid'] ?? null;
                $data['openid'] = $oauthUser['openid'];
                $data['session_key'] = $oauthUser['session_key'];
                break;
        }
        return $data;
    }

    /**
     * @param $type 类型，目前仅支持weimini和wechat
     * @param $openid_unionid_arr 第三方数据标识包括unionid和openid
     * @return string
     */
    public function isUserExist($type,$openid_unionid_arr){
        $user="";
        if ($openid_unionid_arr['unionid']) {
            $user = User::where('unionid', $openid_unionid_arr['unionid'])->first();
        }
        if (!$user){
            switch ($type){
                case 'wechat':
                    $user = User::where('web_openid', $openid_unionid_arr['openid'])->first();
                    break;
                case "weimini":
                    $user = User::where('mini_openid', $openid_unionid_arr['openid'])->first();
                    break;
            }
        }
        return $user;
    }

    /**
     * @param $type 类型，目前仅支持wechat、weimini
     * @param $openid_unionid_arr 第三方标识openid和unionid以及头像路径和第三方session等
     * @param $user 用户模型
     */
    public function updateUserInfo($type,$openid_unionid_arr,$user){
        switch ($type){
            case "wechat":
                    //没有微信浏览器端的openid呢但是有unionid，说明在其他微信端登录过
                    if (!$user->web_openid){
                        $user->web_openid = $openid_unionid_arr['openid'];
                        $user->wx_web_session_key = $openid_unionid_arr['session_key'];
                        $user->avatar = $openid_unionid_arr['avatar'];
                        //更新客户的微信浏览器端的相关信息
                        $user->save();
                    }
                break;
            case "weimini":
                    //没有微信小程序openid  有unionid，说明在其他微信端登录过
                    if (!$user->mini_openid){
                        $user->mini_openid = $openid_unionid_arr['openid'];
                        $user->wx_mini_session_key = $openid_unionid_arr['session_key'];
                        //更新客户相关的微信小程序端的信息
                        $user->save();
                    }
                break;
        }
    }

    /**
     * @param $type 类型，目前仅支持wechat和weimini
     * @param $openid_unionid_arr 第三方unionid和openid
     * @return string 返回包含用户第三方信息value的随机key
     */
    public function CreateThirdIdKey($type,$openid_unionid_arr){
        $key = 'unionid_'.Str::random(15);
        switch ($type){
            case "wechat":
                    $expiredAt = now()->addMinutes(120);
                    // 缓存用户端标识 120分钟过期。
                    \Cache::put($key,
                        ['unionid' => $openid_unionid_arr['unionid'], 'wx_web_session_key' => $openid_unionid_arr['session_key'],
                            "web_openid"=>$openid_unionid_arr['openid'],"avatar"=>$openid_unionid_arr['avatar']],
                        $expiredAt);
                break;
            case "weimini":
                    $expiredAt = now()->addMinutes(120);
                    // 缓存用户端标识 120分钟过期。
                    \Cache::put($key,
                        ['mini_openid' => $openid_unionid_arr['openid'], 'unionid' => $openid_unionid_arr['unionid'],
                            "wx_mini_session_key"=>$openid_unionid_arr['session_key']],
                        $expiredAt);
                    break;
        }
        return $key;
    }
}
